//
// Created by Pulsar on 2021/1/8.
//

#include <hkvqcore/driver/driver.h>
#include <hkvqcore/python/convert_function.h>
#include<exception>

namespace hkvqcore {
    namespace driver {
        Driver::Driver(int index) {
            IS_IPCAM = false;
            cap = new Capture(index);
        }

        Driver::Driver(const std::string &ip_address, const std::string &username, const std::string &password,
                       int Port, int channel, int stream_type) {
            IS_IPCAM = true;
            hkcap = new HKCamDriver(ip_address, username, password, Port, channel, stream_type);
            hkcap->InitHKNetSDK();
        }

        Driver::Driver(const std::string &video_file) {
            IS_IPCAM = false;
            cap = new Capture(video_file);
        }

        data_struct::CamHandle Driver::Init() {
            INIT_FLAG = true;
            if (IS_IPCAM) {
                return (long) hkcap->Init();
            } else {
                return cap->Init();
            }
        }

        pybind11::array_t<unsigned char> Driver::Read(long handel = NULL) {
            if (!INIT_FLAG) {
                throw new std::exception("You Must Init Before you want to run driver");
            }
            cv::Mat frame;
            if (IS_IPCAM) {
                frame = hkcap->Read(handel);
            } else {
                frame = cap->Read();
            }
            return python::cv_mat_uint8_3c_to_numpy(frame);
        }

        void Driver::Release() {
            if (!INIT_FLAG) {
                throw new std::exception("You Must Init Before you want to run driver");
            }
            if (IS_IPCAM) {
                hkcap->ReleaseCamera();
            } else {
                cap->Release();
            }
        }

        cv::Mat Driver::ReadMat(long handel = NULL) {
            if (!INIT_FLAG) {
                throw new std::exception("You Must Init Before you want to run driver");
            }
            if (IS_IPCAM) {
                return hkcap->Read(handel);
            } else {
                return cap->Read();
            }
        }


    }
}